{
 "cells": [
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "Objects have individuality, and multiple names (in multiple scopes) can be bound to the same object."
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "A *namespace* is a mapping from names to objects. \n",
    "\n",
    "从名字到对象的映射."
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "Any name following a dot is a *attribute*.\n",
    "\n",
    "Modules object.\n",
    "\n",
    "Attributes may be read-only or writable. "
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "Namespaces are created at different moments and have different lifetimes. "
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "A *scope* is a textual region of a Python program where a namespace is directly accessible. \n",
    "\n",
    "*scope* 是一个 Python 程序的文本区域, 在这个区域里可以直接访问一个 namespace.\n",
    "\n",
    "* the innermost scope\n",
    "* the scopes of any **enclosing functions**.\n",
    "* the next-to-last scope current module's global names.\n",
    "* the outermost scope (searched last) is the namespace containing built-in names\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 1,
   "metadata": {
    "collapsed": false
   },
   "outputs": [
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "After local assignment: test spam\n",
      "After nonlocal assignment: nonlocal spam\n",
      "After global assignment: nonlocal spam\n",
      "In global scope: global spam\n"
     ]
    }
   ],
   "source": [
    "def scope_test():\n",
    "    def do_local():\n",
    "        spam = \"local spam\"\n",
    "\n",
    "    def do_nonlocal():\n",
    "        nonlocal spam\n",
    "        spam = \"nonlocal spam\"\n",
    "\n",
    "    def do_global():\n",
    "        global spam\n",
    "        spam = \"global spam\"\n",
    "\n",
    "    spam = \"test spam\"\n",
    "    do_local()\n",
    "    print(\"After local assignment:\", spam)\n",
    "    do_nonlocal()\n",
    "    print(\"After nonlocal assignment:\", spam)\n",
    "    do_global()\n",
    "    print(\"After global assignment:\", spam)\n",
    "\n",
    "scope_test()\n",
    "print(\"In global scope:\", spam)"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "Class objects support two kinds of operations: \n",
    "\n",
    "* attribute references \n",
    "* instantiation.\n",
    "\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 3,
   "metadata": {
    "collapsed": false
   },
   "outputs": [
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "16\n"
     ]
    }
   ],
   "source": [
    "class Complex:\n",
    "    def __init__(self, realpart, imagpart):\n",
    "        self.r = realpart\n",
    "        self.i = imagpart\n",
    "        \n",
    "x = Complex(3.0, -4.5)\n",
    "x.r, x.i\n",
    "x.counter = 1\n",
    "while x.counter < 10:\n",
    "    x.counter = x.counter*2\n",
    "print(x.counter)\n",
    "del x.counter"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "There are two kinds of valid attribute names, **data attributes** and **methods**.\n",
    "\n",
    "class instance objects\n",
    "\n",
    "method object\n",
    "function object \n",
    "\n",
    "Instance variable\n",
    "Class variables\n",
    "\n",
    "Name mangling, 名字校正\n",
    "\n",
    "iterator `__next__`\n",
    "\n",
    "Generators are a simple and powerful tool for creating iterators. \n",
    "\n",
    "generator expressions\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 5,
   "metadata": {
    "collapsed": false
   },
   "outputs": [
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "canine\n",
      "canine\n",
      "Fido\n",
      "Buddy\n"
     ]
    }
   ],
   "source": [
    "class Dog:\n",
    "\n",
    "    kind = 'canine'         # class variable shared by all instances\n",
    "\n",
    "    def __init__(self, name):\n",
    "        self.name = name    # instance variable unique to each instance\n",
    "\n",
    "d = Dog('Fido')\n",
    "e = Dog('Buddy')\n",
    "print(d.kind)\n",
    "print(e.kind)\n",
    "print(d.name)\n",
    "print(e.name)"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 7,
   "metadata": {
    "collapsed": false
   },
   "outputs": [
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "<__main__.Employee object at 0x7fae78703828>\n"
     ]
    }
   ],
   "source": [
    "class Employee:\n",
    "    pass\n",
    "\n",
    "john = Employee()  # Create an empty employee record\n",
    "\n",
    "# Fill the fields of the record\n",
    "john.name = 'John Doe'\n",
    "john.dept = 'computer lab'\n",
    "john.salary = 1000\n",
    "print(john)"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 8,
   "metadata": {
    "collapsed": false
   },
   "outputs": [
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "B\n",
      "C\n",
      "D\n"
     ]
    }
   ],
   "source": [
    "class B(Exception):\n",
    "    pass\n",
    "class C(B):\n",
    "    pass\n",
    "class D(C):\n",
    "    pass\n",
    "\n",
    "for cls in [B, C, D]:\n",
    "    try:\n",
    "        raise cls()\n",
    "    except D:\n",
    "        print(\"D\")\n",
    "    except C:\n",
    "        print(\"C\")\n",
    "    except B:\n",
    "        print(\"B\")"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 10,
   "metadata": {
    "collapsed": false
   },
   "outputs": [
    {
     "data": {
      "text/plain": [
       "<str_iterator at 0x7fae787109b0>"
      ]
     },
     "execution_count": 10,
     "metadata": {},
     "output_type": "execute_result"
    }
   ],
   "source": [
    "s = 'abc'\n",
    "it = iter(s)\n",
    "it"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 11,
   "metadata": {
    "collapsed": false
   },
   "outputs": [
    {
     "data": {
      "text/plain": [
       "'a'"
      ]
     },
     "execution_count": 11,
     "metadata": {},
     "output_type": "execute_result"
    }
   ],
   "source": [
    "next(it)"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 12,
   "metadata": {
    "collapsed": false
   },
   "outputs": [
    {
     "data": {
      "text/plain": [
       "'b'"
      ]
     },
     "execution_count": 12,
     "metadata": {},
     "output_type": "execute_result"
    }
   ],
   "source": [
    "next(it)"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 13,
   "metadata": {
    "collapsed": false
   },
   "outputs": [
    {
     "data": {
      "text/plain": [
       "'c'"
      ]
     },
     "execution_count": 13,
     "metadata": {},
     "output_type": "execute_result"
    }
   ],
   "source": [
    "next(it)\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 14,
   "metadata": {
    "collapsed": false
   },
   "outputs": [
    {
     "ename": "StopIteration",
     "evalue": "",
     "output_type": "error",
     "traceback": [
      "\u001b[0;31m---------------------------------------------------------------------------\u001b[0m",
      "\u001b[0;31mStopIteration\u001b[0m                             Traceback (most recent call last)",
      "\u001b[0;32m<ipython-input-14-2cdb14c0d4d6>\u001b[0m in \u001b[0;36m<module>\u001b[0;34m()\u001b[0m\n\u001b[0;32m----> 1\u001b[0;31m \u001b[0mnext\u001b[0m\u001b[0;34m(\u001b[0m\u001b[0mit\u001b[0m\u001b[0;34m)\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n\u001b[0m",
      "\u001b[0;31mStopIteration\u001b[0m: "
     ]
    }
   ],
   "source": [
    "next(it)"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 15,
   "metadata": {
    "collapsed": false
   },
   "outputs": [
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "f\n",
      "l\n",
      "o\n",
      "g\n"
     ]
    }
   ],
   "source": [
    "def reverse(data):\n",
    "    for index in range(len(data)-1, -1, -1):\n",
    "        yield data[index]\n",
    "        \n",
    "for char in reverse('golf'):\n",
    "    print(char)"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 16,
   "metadata": {
    "collapsed": false
   },
   "outputs": [
    {
     "data": {
      "text/plain": [
       "285"
      ]
     },
     "execution_count": 16,
     "metadata": {},
     "output_type": "execute_result"
    }
   ],
   "source": [
    "sum(i*i for i in range(10))"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 17,
   "metadata": {
    "collapsed": false
   },
   "outputs": [
    {
     "data": {
      "text/plain": [
       "260"
      ]
     },
     "execution_count": 17,
     "metadata": {},
     "output_type": "execute_result"
    }
   ],
   "source": [
    "xvec = [10, 20, 30]\n",
    "yvec = [7, 5, 3]\n",
    "sum(x*y for x,y in zip(xvec, yvec))"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 19,
   "metadata": {
    "collapsed": false
   },
   "outputs": [
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "{0: 0.0, 1: 0.01745240643728351, 2: 0.03489949670250097, 3: 0.05233595624294383, 4: 0.0697564737441253, 5: 0.08715574274765817, 6: 0.10452846326765346, 7: 0.12186934340514748, 8: 0.13917310096006544, 9: 0.15643446504023087, 10: 0.17364817766693033, 11: 0.1908089953765448, 12: 0.20791169081775931, 13: 0.224951054343865, 14: 0.24192189559966773, 15: 0.25881904510252074, 16: 0.27563735581699916, 17: 0.29237170472273677, 18: 0.3090169943749474, 19: 0.32556815445715664, 20: 0.3420201433256687, 21: 0.35836794954530027, 22: 0.374606593415912, 23: 0.3907311284892737, 24: 0.40673664307580015, 25: 0.42261826174069944, 26: 0.4383711467890774, 27: 0.45399049973954675, 28: 0.4694715627858908, 29: 0.48480962024633706, 30: 0.49999999999999994, 31: 0.5150380749100542, 32: 0.5299192642332049, 33: 0.5446390350150271, 34: 0.5591929034707469, 35: 0.573576436351046, 36: 0.5877852522924731, 37: 0.6018150231520483, 38: 0.6156614753256582, 39: 0.6293203910498374, 40: 0.6427876096865393, 41: 0.6560590289905072, 42: 0.6691306063588582, 43: 0.6819983600624985, 44: 0.6946583704589973, 45: 0.7071067811865475, 46: 0.7193398003386511, 47: 0.7313537016191705, 48: 0.7431448254773941, 49: 0.754709580222772, 50: 0.766044443118978, 51: 0.7771459614569708, 52: 0.788010753606722, 53: 0.7986355100472928, 54: 0.8090169943749475, 55: 0.8191520442889918, 56: 0.8290375725550417, 57: 0.8386705679454239, 58: 0.848048096156426, 59: 0.8571673007021122, 60: 0.8660254037844386, 61: 0.8746197071393957, 62: 0.8829475928589269, 63: 0.8910065241883678, 64: 0.898794046299167, 65: 0.9063077870366499, 66: 0.9135454576426009, 67: 0.9205048534524403, 68: 0.9271838545667874, 69: 0.9335804264972017, 70: 0.9396926207859083, 71: 0.9455185755993167, 72: 0.9510565162951535, 73: 0.9563047559630354, 74: 0.9612616959383189, 75: 0.9659258262890683, 76: 0.9702957262759965, 77: 0.9743700647852352, 78: 0.9781476007338056, 79: 0.981627183447664, 80: 0.984807753012208, 81: 0.9876883405951378, 82: 0.9902680687415703, 83: 0.992546151641322, 84: 0.9945218953682733, 85: 0.9961946980917455, 86: 0.9975640502598242, 87: 0.9986295347545738, 88: 0.9993908270190958, 89: 0.9998476951563913, 90: 1.0}\n"
     ]
    }
   ],
   "source": [
    "from math import pi, sin\n",
    "sine_table = {x:sin(x*pi/180) for x in range(0, 91)}\n",
    "print(sine_table)"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 20,
   "metadata": {
    "collapsed": false
   },
   "outputs": [
    {
     "ename": "NameError",
     "evalue": "name 'page' is not defined",
     "output_type": "error",
     "traceback": [
      "\u001b[0;31m---------------------------------------------------------------------------\u001b[0m",
      "\u001b[0;31mNameError\u001b[0m                                 Traceback (most recent call last)",
      "\u001b[0;32m<ipython-input-20-410b959c759e>\u001b[0m in \u001b[0;36m<module>\u001b[0;34m()\u001b[0m\n\u001b[0;32m----> 1\u001b[0;31m \u001b[0munique_words\u001b[0m \u001b[0;34m=\u001b[0m \u001b[0mset\u001b[0m\u001b[0;34m(\u001b[0m\u001b[0mword\u001b[0m  \u001b[0;32mfor\u001b[0m \u001b[0mline\u001b[0m \u001b[0;32min\u001b[0m \u001b[0mpage\u001b[0m  \u001b[0;32mfor\u001b[0m \u001b[0mword\u001b[0m \u001b[0;32min\u001b[0m \u001b[0mline\u001b[0m\u001b[0;34m.\u001b[0m\u001b[0msplit\u001b[0m\u001b[0;34m(\u001b[0m\u001b[0;34m)\u001b[0m\u001b[0;34m)\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n\u001b[0m",
      "\u001b[0;31mNameError\u001b[0m: name 'page' is not defined"
     ]
    }
   ],
   "source": [
    "unique_words = set(word  for line in page  for word in line.split())"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "## Wehtting your appetite"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 21,
   "metadata": {
    "collapsed": false
   },
   "outputs": [
    {
     "data": {
      "text/plain": [
       "50"
      ]
     },
     "execution_count": 21,
     "metadata": {},
     "output_type": "execute_result"
    }
   ],
   "source": [
    "price = 10\n",
    "tax = 5\n",
    "price*tax"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 22,
   "metadata": {
    "collapsed": false
   },
   "outputs": [
    {
     "data": {
      "text/plain": [
       "60"
      ]
     },
     "execution_count": 22,
     "metadata": {},
     "output_type": "execute_result"
    }
   ],
   "source": [
    "price + _"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 24,
   "metadata": {
    "collapsed": false
   },
   "outputs": [
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "c:\\file\\name\n"
     ]
    }
   ],
   "source": [
    "print(r'c:\\file\\name')"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 25,
   "metadata": {
    "collapsed": false
   },
   "outputs": [
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "Usage: thingy [OPTIONS]\n",
      "     -h                        Display this usage message\n",
      "     -H hostname               Hostname to connect to\n",
      "\n"
     ]
    }
   ],
   "source": [
    "print(\"\"\"\\\n",
    "Usage: thingy [OPTIONS]\n",
    "     -h                        Display this usage message\n",
    "     -H hostname               Hostname to connect to\n",
    "\"\"\")"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    " +---+---+---+---+---+---+\n",
    " | P | y | t | h | o | n |\n",
    " +---+---+---+---+---+---+\n",
    " 0   1   2   3   4   5   6\n",
    "-6  -5  -4  -3  -2  -1\n",
    "\n",
    "string is immutable"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 27,
   "metadata": {
    "collapsed": false
   },
   "outputs": [
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "[(0, 'Spring'), (1, 'Summer'), (2, 'Fall'), (3, 'Winter')]\n",
      "[(1, 'Spring'), (2, 'Summer'), (3, 'Fall'), (4, 'Winter')]\n"
     ]
    }
   ],
   "source": [
    "seasons = ['Spring', 'Summer', 'Fall', 'Winter']\n",
    "print(list(enumerate(seasons)))\n",
    "print(list(enumerate(seasons, start=1)))"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 28,
   "metadata": {
    "collapsed": false
   },
   "outputs": [
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "\n"
     ]
    }
   ],
   "source": [
    "print()"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "* Use 4-space indentation, and no tabs.\n",
    "\n",
    "4 spaces are a good compromise between small indentation (allows greater nesting depth) and large indentation (easier to read). Tabs introduce confusion, and are best left out.\n",
    "\n",
    "* Wrap lines so that they don’t exceed 79 characters.\n",
    "\n",
    "This helps users with small displays and makes it possible to have several code files side-by-side on larger displays.\n",
    "\n",
    "* Use blank lines to separate functions and classes, and larger blocks of code inside functions.\n",
    "\n",
    "* When possible, put comments on a line of their own.\n",
    "\n",
    "* Use docstrings.\n",
    "\n",
    "* Use spaces around operators and after commas, but not directly inside bracketing constructs: a = f(1, 2) + g(3, 4).\n",
    "\n",
    "* Name your classes and functions consistently; the convention is to use CamelCase for classes and lower_case_with_underscores for functions and methods. Always use self as the name for the first method argument (see A First Look at Classes for more on classes and methods).\n",
    "\n",
    "* Don’t use fancy encodings if your code is meant to be used in international environments. Python’s default, UTF-8, or even plain ASCII work best in any case.\n",
    "\n",
    "* Likewise, don’t use non-ASCII characters in identifiers if there is only the slightest chance people speaking a different language will read or maintain the code.\n",
    "\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {
    "collapsed": true
   },
   "outputs": [],
   "source": []
  }
 ],
 "metadata": {
  "kernelspec": {
   "display_name": "Python 3",
   "language": "python",
   "name": "python3"
  },
  "language_info": {
   "codemirror_mode": {
    "name": "ipython",
    "version": 3
   },
   "file_extension": ".py",
   "mimetype": "text/x-python",
   "name": "python",
   "nbconvert_exporter": "python",
   "pygments_lexer": "ipython3",
   "version": "3.5.2"
  },
  "latex_envs": {
   "LaTeX_envs_menu_present": true,
   "bibliofile": "biblio.bib",
   "cite_by": "apalike",
   "current_citInitial": 1,
   "eqLabelWithNumbers": true,
   "eqNumInitial": 0
  }
 },
 "nbformat": 4,
 "nbformat_minor": 1
}
